package com.vegetable.modules.controller.wxApp;

import cn.binarywang.wx.miniapp.api.WxMaService;
import cn.binarywang.wx.miniapp.bean.WxMaJscode2SessionResult;
import cn.binarywang.wx.miniapp.bean.WxMaPhoneNumberInfo;
import cn.binarywang.wx.miniapp.bean.WxMaUserInfo;
import cn.binarywang.wx.miniapp.util.WxMaConfigHolder;
import cn.hutool.core.util.ObjectUtil;
import com.alibaba.fastjson.JSONObject;
import com.vegetable.common.utils.R;
import com.vegetable.modules.controller.AbstractController;
import com.vegetable.modules.entity.sys.SysUserEntity;
import com.vegetable.modules.entity.wx.po.QueryWXPhonePO;
import com.vegetable.modules.service.sys.SysUserService;
import com.vegetable.modules.service.sys.SysUserTokenService;
import io.swagger.annotations.Api;
import lombok.extern.slf4j.Slf4j;
import me.chanjar.weixin.common.error.WxErrorException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 微信小程序用户接口
 *
 * @author <a href="https://github.com/binarywang">Binary Wang</a>
 */
@RestController
@Slf4j
@RequestMapping("/wx/")
@Api(value = "微信小程序", tags = "微信小程序")
public class WxMaUserController  extends AbstractController {
    @Autowired
    private  WxMaService wxMaService;
    @Autowired
    private SysUserService sysUserService;
    @Autowired
    private SysUserTokenService sysUserTokenService;

    @GetMapping("/login")
    public R login(String jsCode) {
        log.info("wx登录jsCode参数：{}", jsCode);
        String appId = wxMaService.getWxMaConfig().getAppid();
        if (!wxMaService.switchover(appId)) {
            throw new IllegalArgumentException(String.format("未找到对应appid=[%s]的配置，请核实！", appId));
        }
        try {
            WxMaJscode2SessionResult session = wxMaService.getUserService().getSessionInfo(jsCode);
            if (session == null || session.getOpenid() == null || session.getSessionKey() == null) {
                return R.fail("微信信息获取失败");
            }
            String openId = session.getOpenid();
            SysUserEntity user = sysUserService.queryByOpenId(openId);
            log.info("根据openId{}查询到的用户是:{},微信返回的sk是：{}", openId, user, session.getSessionKey());
            if(ObjectUtil.isNotNull(user)){
                return sysUserTokenService.createToken(user);
            }else{
                // 绑定手机
                Map<String, Object> result = new HashMap<>();
                result.put("openId", openId);
                result.put("sessionKey", session.getSessionKey());
                return R.data(result);
            }
//            log.info(session.getSessionKey());
//            log.info(session.getOpenid());
//            //TODO 可以增加自己的逻辑，关联业务相关数据
//            return R.data(session);
        } catch (WxErrorException e) {
            log.error(e.getMessage(), e);
            return R.fail("小程序授权登陆失败");
        } finally {
            WxMaConfigHolder.remove();//清理ThreadLocal
        }
    }
    /**
     * 登陆接口
     */
    @PostMapping("/exchangeToken")
    public R exchangeToken(@RequestBody QueryWXPhonePO po) {
        log.info("wx登录exchangeToken方法参数：{}", po);
        String openId = po.getOpenId();
        SysUserEntity user = sysUserService.queryByOpenId(openId);
        if(ObjectUtil.isNotNull(user)){
            return sysUserTokenService.createToken(user);
        }else{
            WxMaPhoneNumberInfo phoneNoInfo = wxMaService.getUserService().getPhoneNoInfo(po.getSessionKey(), po.getEncryptedData(), po.getIv());
            String phone = phoneNoInfo.getPhoneNumber();
            SysUserEntity sysUser = sysUserService.queryByMobile(phone);
            if(ObjectUtil.isNull(sysUser)){
//                String testMobile = "13416472917";
//                SysUserEntity userEntity = new SysUserEntity();
//                userEntity.setUserId(visitor.getUserId());
//                userEntity.setOpenId(openId);
//                sysUserService.updateById(userEntity);
                // 创建游客账号
                sysUserService.createVisitor(phone, openId);
                SysUserEntity visitor = sysUserService.queryByMobile(phone);
                return sysUserTokenService.createToken(visitor);
//                return R.fail("用户[" + phone + "]还没有注册，请联系管理员");
            }else {
                SysUserEntity userEntity = new SysUserEntity();
                userEntity.setUserId(sysUser.getUserId());
                userEntity.setOpenId(openId);
                sysUserService.updateById(userEntity);
                return sysUserTokenService.createToken(sysUser);
            }
        }
    }

    /**
     * <pre>
     * 获取用户信息接口
     * </pre>
     */
    @PostMapping("/info")
    public String info(@RequestBody QueryWXPhonePO po) {
        String appId = wxMaService.getWxMaConfig().getAppid();
        if (!wxMaService.switchover(appId)) {
            throw new IllegalArgumentException(String.format("未找到对应appid=[%s]的配置，请核实！", appId));
        }

        // 用户信息校验
//        if (!wxMaService.getUserService().checkUserInfo(sessionKey, rawData, signature)) {
//            WxMaConfigHolder.remove();//清理ThreadLocal
//            return "user check failed";
//        }

        // 解密用户信息
        WxMaUserInfo userInfo = wxMaService.getUserService().getUserInfo(po.getSessionKey(), po.getEncryptedData(), po.getIv());
        WxMaConfigHolder.remove();//清理ThreadLocal
        return JSONObject.toJSONString(userInfo);
    }

    /**
     * <pre>
     * 获取用户绑定手机号信息
     * </pre>
     */
    @PostMapping("/phone")
    public String phone(@RequestBody QueryWXPhonePO po) {
        String appId = wxMaService.getWxMaConfig().getAppid();
        if (!wxMaService.switchover(appId)) {
            throw new IllegalArgumentException(String.format("未找到对应appid=[%s]的配置，请核实！", appId));
        }

        // 用户信息校验
//        if (!wxMaService.getUserService().checkUserInfo(sessionKey, rawData, signature)) {
//            WxMaConfigHolder.remove();//清理ThreadLocal
//            return "user check failed";
//        }

        // 解密
        WxMaPhoneNumberInfo phoneNoInfo = wxMaService.getUserService().getPhoneNoInfo(po.getSessionKey(), po.getEncryptedData(), po.getIv());
        WxMaConfigHolder.remove();//清理ThreadLocal
        // 获取手机号并验证数据库里的手机号是否存在
        // 如果存在，生成token返回前端
        return JSONObject.toJSONString(phoneNoInfo);
    }
    @GetMapping("/permissions")
    public R permissions() {
        List<String> permissions = new ArrayList<>();
        permissions.add("delivery");
        permissions.add("area_list");
        permissions.add("task");
        permissions.add("shipment");
        return R.data(permissions);
    }

}
